package com.welldone.service;

import java.io.InputStream;
import java.util.Properties;

import javax.naming.InitialContext;
import javax.sql.DataSource;

import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import org.springframework.jdbc.datasource.DriverManagerDataSource;
import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.support.TransactionCallback;
import org.springframework.transaction.support.TransactionTemplate;

/**
 * 数据库操作封闭对象
 */
public class DBService {

	private static DataSource dataSource = null;
	private static JdbcTemplate jdbcTemplate = null;
	private static DataSourceTransactionManager dataSourceTransactionManager = null;
	private static TransactionTemplate transactionTemplate = null;
	private static String jndiName = "";
	private static String driverClassName = "";
	private static String url = "";
	private static String username = "";
	private static String password = "";

	static {
		try {
			Properties prop = new Properties();  
			InputStream inStream = DBService.class.getClassLoader().getResourceAsStream("dbconfig.properties");  
			prop.load(inStream);
			inStream.close();
			jndiName = prop.getProperty("jndiName").trim();  
			driverClassName = prop.getProperty("driverClassName").trim();  
			url = prop.getProperty("url").trim();  
			username = prop.getProperty("username").trim();  
			password = prop.getProperty("password").trim();  
			String flag = prop.getProperty("flag").trim();
			if(flag.equals("1")) {//生产环境
				dataSource = getDataSource4product();
			}
			if("2".equals(flag)) {//开发环境
				dataSource = getDataSource4development();
			}
			
			jdbcTemplate = new JdbcTemplate(dataSource);
			dataSourceTransactionManager = new DataSourceTransactionManager(
					dataSource);
			transactionTemplate = new TransactionTemplate(
					dataSourceTransactionManager);
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	private static DataSource getDataSource4product() throws Exception {
		InitialContext ctx = new InitialContext();
		DataSource ds = (DataSource) ctx.lookup(jndiName);
		return ds;
	}

	private static DataSource getDataSource4development() throws Exception {
		DriverManagerDataSource ds = new DriverManagerDataSource();
		ds.setDriverClassName(driverClassName);
		ds.setUrl(url);
		ds.setUsername(username);
		ds.setPassword(password);
		return ds;
	}

	private DBService() {

	}

	public static JdbcTemplate getJdbcTemplate() {
		return jdbcTemplate;
	}

	public static TransactionTemplate getTransactionTemplate() {
		return transactionTemplate;
	}

	/**
	 * 数据库事务处理（批处理方式）
	 * @param sqlArray SQL数据
	 */
	public static void execTransaction(final String[] sqlArray) {
		TransactionTemplate tt = DBService.getTransactionTemplate();
		tt.execute(new TransactionCallback() {
			/* 
			 * 此方法内的数据库操作在同一事务中
			 */
			public Object doInTransaction(TransactionStatus status) {
				JdbcTemplate j = getJdbcTemplate();
				j.batchUpdate(sqlArray);
				return null;
			}
		});
	}
	
	/**
	 * 数据库事务处理（预处理方式）
	 * @param sqlArray SQL数据
	 * @param sqlParameter 参数数组
	 */
	public static void execTransaction(final String[] sqlArray,final Object[][] sqlParameter) {
		TransactionTemplate tt = DBService.getTransactionTemplate();
		tt.execute(new TransactionCallback() {
			/* 
			 * 此方法内的数据库操作在同一事务中
			 */
			public Object doInTransaction(TransactionStatus status) {
				JdbcTemplate j = DBService.getJdbcTemplate();
				for(int i=0;i<sqlArray.length;i++){
					j.update(sqlArray[i], sqlParameter[i]);
				}
				return null;
			}
		});
	}
	
	
	/**
	 * 样例--数据库事务操作（批处理方式）
	 */
	@SuppressWarnings("unused")
	private void testTransaction4sqlArray() {
		String[] sql = new String[2];
		sql[0] = "update fuhe_test set c_char=2 where c_no=1";
		sql[1] = "update fuhe_test set C_VCHAR2='mmx' where id=1";
		execTransaction(sql);
	}

	/**
	 * 样例--数据库事务操作样例（预处理方式）
	 */
	@SuppressWarnings("unused")
	private void testTransaction4prepared() {
		String[] sql = new String[2];
		Object[][] sqlParameter=new Object[2][];
		sql[0] = "update test set clob1=333 where id=?";
		sqlParameter[0]=new Object[]{new Integer(1)};
		sql[1] = "update test set clob1=444 where id1=?";
		sqlParameter[1]=new Object[]{new Integer(2)};
		execTransaction(sql,sqlParameter);
	}
}














